#!/usr/bin/env python
#
# Copyright 2009 Facebook
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.

import os.path
import re
import tornado.httpserver
import tornado.ioloop
import tornado.web
import unicodedata
import tornado.locale

from tornado.options import define, options
from jinja2 import Environment, FileSystemLoader, FileSystemBytecodeCache
from models import db
from models.user import User
from sqlalchemy import and_
from forms.register import RegisterForm

define("port", default=8888, help="run on the given port", type=int)
define("tforms_locale", type=tornado.locale.CSVLocale)

class Application(tornado.web.Application):
    def __init__(self):
        handlers = [
            (r"/register", RegisterHandler),
            (r"/users", ListUserHandler),
            (r"/login", LoginHandler),
        ]
        settings = dict(
            blog_title=u"Tornado Blog",
            template_path=os.path.join(os.path.dirname(__file__), "templates"),
            static_path=os.path.join(os.path.dirname(__file__), "static"),
            xsrf_cookies=True,
            cookie_secret="__TODO:_GENERATE_YOUR_OWN_RANDOM_VALUE_HERE__",
            autoescape=None,
        )
        tornado.web.Application.__init__(self, handlers, **settings)
        tornado.locale.load_translations(os.path.join(os.path.dirname(__file__), "locale"))
        tornado.locale.set_default_locale('zh_CN')
        # Have one global connection to the blog DB across all handlers
        db.init_db()
        self.db = db.session
        self.jinja2_env = Environment(loader = FileSystemLoader('templates'))

class BaseHandler(tornado.web.RequestHandler):
    @property
    def db(self):
        return self.application.db

    @property
    def jinja2_env(self):
        return self.application.jinja2_env

    def prepare(self):
        options.tforms_locale = self.locale

    def get_current_user(self):
        user_id = self.get_secure_cookie("userid")
        if not user_id: return None
        return self.db.query(User).filter(User.id == user_id).one()

    def to_render(self, template_, **kwargs):
        template = self.jinja2_env.get_template(template_)
        if kwargs is None:
            self.write(template.render())
        else:
            self.write(template.render(kwargs))

class RegisterHandler(BaseHandler):
    def get(self):
        form = RegisterForm()
        self.to_render("register.html", form = form, xsrf_form_html = self.xsrf_form_html)

    def post(self):
        form = RegisterForm(self.request.arguments)
        if form.validate():
            u = User(form.username.data, form.realname.data, form.password.data)
            self.db.add(u)
            self.db.commit()
            self.write("success")
        else:
            self.to_render("register.html", form=form, xsrf_form_html = self.xsrf_form_html)

class ListUserHandler(BaseHandler):
    def get(self):
        users = self.db.query(User).all()
        print users
        self.to_render("listusers.html", users=users)

class LoginHandler(BaseHandler):
    def get(self):
        self.to_render("login.html", xsrf_form_html = self.xsrf_form_html, message=None)

    def post(self):
        username = self.get_argument("username")
        passwd = self.get_argument("passwd")
        u = self.db.query(User).filter(and_(User.name == username, User.password == passwd)).first()
        if u:
            self.set_secure_cookie("userid", unicode(u.id))
            self.redirect("/users")
        else:
            self.to_render("login.html", xsrf_form_html = self.xsrf_form_html, message="username and password not match")

def main():
    tornado.options.parse_command_line()
    http_server = tornado.httpserver.HTTPServer(Application())
    http_server.listen(options.port)
    tornado.ioloop.IOLoop.instance().start()

if __name__ == "__main__":
    main()
